<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>观察者模式</title>
    <style>
        div{
            width: 100%;
            height: 100px;
            clear: both;
            border: 1px solid red;
            margin: 10px 0;
        }
    </style>
</head>
<body>
<label for="sex"></label>
<select name="sex" id="sex">
    <option value="male">男性</option>
    <option value="female">女性</option>
</select>
<button onclick="t1()">不观察内容区了</button>
<div id="content">内容</div>
<div id="hobe">爱好</div>
<div id="buy">推荐购买</div>
</body>
</html>
<script>
    //观察者模式---》主要减少功能间的耦合度，增加扩展性，当被观察者变化时想增加一项功能，直接新增一个观察者实现即可
    // 定义对象间的一种一对多的依赖关系，当一个对象的状态发生改变时，所有依赖于它的对象都得到通知并被自动更新
    /************************************被观察者部分***************************************************/

    //声明被观察者

    var obj = document.getElementById('sex');

    //声明obj的观察者
    obj.observer = {};

    //添加观察者
    obj.attach = function (key, val) {
        this.observer[key] = val;
    };

    //删除观察者
    obj.detach = function (key) {
        delete this.observer[key];
    };

    //为被观察者新增《通知观察者》方法notify
    obj.notify = function () {
        for(var key in this.observer){
            //通知观察者执行change
            this.observer[key].change(this);
        }
    };

    /*********************************观察者部分******************************************************/

    //观察者1绑定change方法
    var content = document.getElementById('content');
    content.change = function (obj) {
        var value = obj.value;
        if (value == 'male') {
            this.style.backgroundColor = '#FFF';
            this.innerHTML = 'haha111';
        } else if (value == 'female') {
            this.style.backgroundColor = 'red';
            this.innerHTML = 'heihei111';
        }
    };

    //观察者2绑定change方法
    var hobe = document.getElementById('hobe');
    hobe.change = function (obj) {
        var value = obj.value;
        if (value == 'male') {
            this.style.backgroundColor = '#000';
            this.innerHTML = 'haha2222';
        } else if (value == 'female') {
            this.style.backgroundColor = 'red';
            this.innerHTML = 'heihei222';
        }
    };

    //新增观察者3绑定change方法
    var buy = document.getElementById('buy');
    buy.change = function (obj) {
        var value = obj.value;
        if (value == 'male') {
            this.style.backgroundColor = 'gray';
            this.innerHTML = 'haha333';
        } else if (value == 'female') {
            this.style.backgroundColor = 'red';
            this.innerHTML = 'heihei333';
        }
    };

    /*********************************执行部分******************************************************/
    //添加观察者
    obj.attach('content',content);
    obj.attach('hobe',hobe);
    obj.attach('buy',buy);
    //obj变化，触发通知
    obj.onchange = obj.notify;

    //删除观察者
    function t1() {
        obj.detach('content');
    }
</script>